package mutris.client.board;

import java.util.LinkedHashMap;
import java.util.Observable;
import java.util.Set;


public class Board extends Observable {

	static private final int TOP_MIN = -5;
	
	
	static public final int DEFAULT_WIDTH = 10;
	static public final int DEFAULT_HEIGHT = 22;
	
	
	private int width;
	private int height;
	
	private LinkedHashMap<BlockPoint,Block> blocks;
	
	
	
	public Board() {
		this(DEFAULT_WIDTH, DEFAULT_HEIGHT);
	}
	
	public Board(int width, int height) {
		this.width = width;
		this.height = height;
		
		this.blocks = new LinkedHashMap<BlockPoint, Block>();
	}
	
	
	public int getWidth() {
		return width;
	}
	
	
	public int getHeight() {
		return height;
	}
	
	
	private void checkPoint(BlockPoint p) {
		if (p.x < 0 || p.x >= width || p.y < TOP_MIN || p.y >= height) {
			throw new IllegalArgumentException("Invalid coordinate: " + p.x + ", " + p.y);
		}
	}
	
	
	public Block getBlock(int x, int y) {
		return getBlock(new BlockPoint(x, y));
	}
	
	public Block getBlock(BlockPoint p) {
		checkPoint(p);

		return blocks.get(p);
	}
	
	
	public void setBlock(int x, int y, Block block) {
		setBlock(new BlockPoint(x, y), block);
	}
	
	public void setBlock(BlockPoint p, Block block) {
		if (null == block) {
			throw new NullPointerException("Use the method clearBlock() to rest a block");
		}
		checkPoint(p);
		
		blocks.put(new BlockPoint(p), block);
		
		setChanged();
	}
	
	public void clearBlock(int x, int y) {
		clearBlock(new BlockPoint(x, y));
	}
	
	public Block clearBlock(BlockPoint p) {
		Block block = null;
		checkPoint(p);
		
		block = blocks.remove(p);
		if (null != block) {
			setChanged();
		}
		
		return block;
	}
	
	public void clearBlocks() {
		blocks.clear();
		
		setChanged();
	}

	public Set<BlockPoint> getPoints() {
		return blocks.keySet();
	}
	
}
